package asteroids.model;

import asteroids.Util;
import be.kuleuven.cs.som.annotate.Basic;

public class Bullet extends CollisionObject{

	public Bullet(double xCoordinate, double yCoordinate, double xVelocity, double yVelocity, double radius,Ship ship,double density) throws OutOfBoundsException, IllegalRadiusException, IllegalDensityException {
		super(xCoordinate, yCoordinate, xVelocity, yVelocity, radius);
		if(isValidDensity(density)){
			this.density = density;
		}
		else {throw new IllegalDensityException("That is an invalid density");}  
		setMass(radius);
		this.ship = ship;
		setMinimumDensity(0);
		setMaximumDensity(Double.MAX_VALUE);
		
	}
	

	//TODO ik zou hier nog een tweede constructor willen die gwn de standaard density aanmaakt, want er is nergens gezegd dat deze density later niet kan veranderen, gwn eerder van nu voor de eenvoud gebruiken we voor elk van dit deze density, maak hier eerder gwn de default constructor van. Probleem is dat deze methode de constructor van collisionobject wilt gebruiken
public Bullet(double xCoordinate, double yCoordinate, double xVelocity, double yVelocity, double radius,Ship ship) throws OutOfBoundsException, IllegalRadiusException {
	super(xCoordinate, yCoordinate, xVelocity, yVelocity, radius);
	setMass(radius);
	this.ship = ship;
	setMinimumDensity(0);
	setMaximumDensity(Double.MAX_VALUE);
	this.density = getGivenDensity();
}

	@Override
	protected double getMinimumMass() {
		return 0;
	}

	@Override
	protected double getMaximumMass() {
		return Double.POSITIVE_INFINITY;
	}

	@Override
	protected CollisionObject getObjectAtColissionPosition(CollisionObject bullet, double timeLapse) {
		double newXCoordinate = bullet.getXVelocity()*timeLapse + bullet.getXCoordinate();
		double newYCoordinate = bullet.getYVelocity()*timeLapse + bullet.getYCoordinate();
		Bullet resultBullet = new Bullet(newXCoordinate,newYCoordinate,bullet.getXVelocity(),bullet.getYVelocity(),bullet.getRadius(),((Bullet) bullet).getShip());
		return resultBullet;
	}

	public Ship getShip(){
		return this.ship;
	}
	
	
	/**
	 * Get the density from the collisionObject;
	 * @return The density of the collisionobject
	 */
	@Basic
	private double getDensity(){
		return this.density;
	}

	
	private boolean isValidDensity(double density) {
		return (Util.fuzzyLessThanOrEqualTo(density, getMinimumDensity()) || !Util.fuzzyLessThanOrEqualTo(density, getMaximumDensity())|| Double.isNaN(density));
	}
	private double getMaximumDensity(){
		return this.maximumDensity;
	}
	private double getMinimumDensity(){
		return this.minimumDensity;
	}
	
	private void setMaximumDensity(double maxDensity){
		this.maximumDensity = maxDensity;
	}
	
	private void setMinimumDensity(double minDensity){
		this.minimumDensity = minDensity;
	}

	private double minimumDensity;
	private double maximumDensity;
	
	
	//ik ben niet zeker dat density echt final moet zijn, en gebruik zeker getters en setters ipv direct de velden :)
	//TODO de density mag nie veranderen tijdens het spel volgens mij?
	

	  /**
	   * Return the source of <code>bullet</code>.
	   */
	  public Ship getBulletSource(Bullet bullet){
		  return this.ship;
		  //TODO
		  }
	  private final Ship ship;
	  
	  @Override
	  public void setMass(double radius){
		  this.mass = Math.pow(radius, 3)*4/3/Math.PI*this.getDensity();
	  }
	  
	private double mass;
	private double getGivenDensity(){
		return this.givenDensity;
	}
	private double givenDensity = 7.8*Math.pow(10, 12);
	private final double density;


	@Override
	public void collisionReactionWith(CollisionObject collisionObject) {
		// TODO Auto-generated method stub
		
	}

}
